﻿using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Text;
using Microsoft.TeamFoundation.WorkItemTracking.Client;
using OfficeOpenXml;

namespace Core
{
    class ResolvedReport : ReportBase
    {
        public void Build(WorkItemCollection workItemCollection)
        {
            Trace.WriteLine("Building resolved report...");

            ExcelPackage pck = Core.OpenExcelFileWithWaiting(Configuration.ReportFilePath);
            if (pck.Workbook.Worksheets.FirstOrDefault(w => w.Name == ReportSettings.ResolvedWorksheet) == null)
                pck.Workbook.Worksheets.Add(ReportSettings.ResolvedWorksheet);
            var ws = pck.Workbook.Worksheets[ReportSettings.ResolvedWorksheet];

            int row = 1;
            List<int> alreadyPresent = new List<int>();
            while (ws.Cells[row, 1].Value != null)
            {
                int id;
                if (Int32.TryParse(ws.Cells[row, 1].Value.ToString(), out id))
                    alreadyPresent.Add(id);
                row++;
            }

            foreach (WorkItem workItem in workItemCollection)
            {
                if ((workItem.Type.Name == "Task" ||
                    workItem.Type.Name == "Bug") &&
                    StateClosedResolved(workItem.State) &&
                    !alreadyPresent.Contains(workItem.Id))
                {
                    // Fill row
                    ws.Cells[row, ReportSettings.IdColumn].Value =
                    workItem.Id;
                    ws.Cells[row, ReportSettings.WorkItemTypeColumn].Value =
                        workItem.Fields[CoreField.WorkItemType].Value;
                    ws.Cells[row, ReportSettings.TitleColumn].Value =
                        workItem.Title;
                    ws.Cells[row, ReportSettings.AssignedToColumn].Value =
                        workItem.Fields[CoreField.AssignedTo].Value.ToString();
                    ws.Cells[row, ReportSettings.StateColumn].Value =
                        workItem.State;
                    if (workItem.Type.FieldDefinitions.TryGetByName(ReportSettings.OriginalEstimateName) != null)
                    {
                        ws.Cells[row, ReportSettings.OriginalEstimateColumn].Value =
                            workItem.Fields[ReportSettings.OriginalEstimateName].Value;
                    }
                    if (workItem.Type.FieldDefinitions.TryGetByName(ReportSettings.CompletedWorkName) != null)
                    {
                        ws.Cells[row, ReportSettings.CompletedWorkColumn].Value =
                            workItem.Fields[ReportSettings.CompletedWorkName].Value;
                    }
                    if (workItem.Type.FieldDefinitions.TryGetByName(ReportSettings.RemainingWorkName) != null)
                    {
                        ws.Cells[row, ReportSettings.RemainingWorkColumn].Value =
                            workItem.Fields[ReportSettings.RemainingWorkName].Value;
                    }
                    if (workItem.Type.FieldDefinitions.TryGetByName(ReportSettings.StackRankName) != null)
                    {
                        ws.Cells[row, ReportSettings.StackRankColumn].Value =
                            workItem.Fields[ReportSettings.StackRankName].Value;
                    }
                    ws.Cells[row, ReportSettings.StackRankColumn + 1].Value =
                            ((DateTime)workItem.Fields[CoreField.ChangedDate].Value);
                    ws.Cells[row, ReportSettings.StackRankColumn + 2].Value =
                            GetFixedBy(workItem);

                    row++;
                }
            }

            pck.Save();
        }

        private string GetFixedBy(WorkItem workItem)
        {
            var hoursResolved = new Dictionary<string, double>();
            for(int i=1; i < workItem.Revisions.Count; i++)
            {
                double oldValue = 0;
                if ( workItem.Revisions[i - 1].Fields[ReportSettings.RemainingWorkName].Value != null)
                    oldValue = (double)workItem.Revisions[i - 1].Fields[ReportSettings.RemainingWorkName].Value;
                double newValue = 0;
                if (workItem.Revisions[i].Fields[ReportSettings.RemainingWorkName].Value != null)
                    newValue = (double) workItem.Revisions[i].Fields[ReportSettings.RemainingWorkName].Value;
                string changedBy = workItem.Revisions[i].Fields[CoreField.ChangedBy].Value.ToString();
                if(oldValue > newValue)
                {
                    if(!hoursResolved.ContainsKey(changedBy))
                        hoursResolved.Add(changedBy, 0);
                    hoursResolved[changedBy] = oldValue - newValue;
                }
            }

            double max = 0;
            string maxName = string.Empty;
            foreach (KeyValuePair<string, double> pair in hoursResolved)
            {
                if (max < pair.Value)
                {
                    max = pair.Value;
                    maxName = pair.Key;
                }
            }
            return maxName;
        }
    }
}
